import { axios } from "./request.js";
import mustache from "./mustache.js";

window.cjs_data = {};
window.customElementDataMap = new Map();
window.customElementsMap = new Map();

// 异步获取模板内容
function getTemplateContent(name) {
  return new Promise((resolve, reject) => {
    axios
      .post("http://localhost:3000/getTemplateContent", { name })
      .then((response) => {
        resolve(response);
      })
      .catch((error) => {
        reject(error);
      });
  });
}

// 异步获取视图名称
function getViewsNames() {
  return new Promise((resolve, reject) => {
    axios
      .get("http://localhost:3000/getViewsNames")
      .then((response) => {
        resolve(response);
      })
      .catch((error) => {
        reject(error);
      });
  });
}

// 定义一个方法来设置数据到 cjs_data
window.setCjsData = (key, data) => {
  Resource(() => {
    cjs_data[key] = data;
  });
};

// 替换模板内容
function replaceTemplate(dom, data) {
  if (dom instanceof Element) {
    let templateContent = dom.innerHTML;

    Resource(() => {
      dom.innerHTML = mustache.render(templateContent, data);
    });
  } else {
    Resource(() => {
      dom = mustache.render(dom, data);
    });
  }
}

// 检查文档状态并执行函数
function Resource(fn) {
  if (document.readyState === "loading") {
    document.addEventListener("DOMContentLoaded", fn);
  } else {
    fn();
  }
}

// 获取元素属性值
window.getProp = async (dom) => {
  return new Promise((resolve, reject) => {
    Resource(() => {
      let myKey = dom.getAttribute("key");
      let foundData = Object.values(cjs_data).find(
        (data) => data.key === myKey
      );
      resolve(foundData);
    });
  });
};

// 获取元素的属性值
function getAtrributeData(dom) {
  return dom.getAttribute("data");
}

// 生成UUID
function generateUUID() {
  return "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g, function (c) {
    var r = (Math.random() * 16) | 0;
    var v = c == "x" ? r : (r & 0x3) | 0x8;
    return v.toString(16);
  });
}

// 渲染自定义元素
function renderElement(elementName, templateString) {
  const doc = new DOMParser().parseFromString(templateString, "text/html");
  let templateTag = doc.querySelector("template");
  let templateContent = templateTag.innerHTML;

  if (!templateTag) {
    console.error("Template element not found in the provided string.");
    return;
  }

  let scriptContent;

  class CustomElement extends HTMLElement {
    constructor() {
      super();

      this.appendChild(document.importNode(templateTag.content, true));

      const styles = doc.querySelectorAll("style");
      styles.forEach((style) => {
        this.appendChild(document.importNode(style, true));
      });

      const scripts = doc.querySelectorAll("script");
      scripts.forEach((script) => {
        scriptContent = script.textContent;
      });
    }

    connectedCallback() {
      let currentElement = this;
      let uuid = generateUUID();
      currentElement.setAttribute("key", uuid);
      customElementsMap.set(uuid, currentElement);

      Resource(() => {
        let currentElement = this;
        let tmp = currentElement.querySelector("div");
        let attributeKey = getAtrributeData(currentElement);

        if (attributeKey) {
          if (cjs_data[attributeKey]) {
            cjs_data[attributeKey].key = currentElement.getAttribute("key");
            let data = cjs_data[attributeKey];
            replaceTemplate(tmp, data);
          } else {
            console.log(
              `Data for attribute key "${attributeKey}" is undefined.`
            );
          }
        } else {
          console.log("Attribute key is missing or null.");
        }
      });

      const firstChild = currentElement.firstChild;
      const textContent = firstChild.textContent.trim();
      let cha = currentElement.querySelector("cha");
      if (cha) {
        if (firstChild.nodeType === 3) {
          currentElement.removeChild(firstChild);
          cha.appendChild(firstChild);
        } else {
          cha.innerHTML = textContent;
        }
      }

      scriptContent = scriptContent?.replace("document", "this");
      eval(scriptContent);
    }
  }

  customElements.define(elementName, CustomElement);
}

// 获取自定义元素
window.getCustomElement = (element) => {
  const uuid = element.getAttribute("key");
  return customElementsMap.get(uuid);
};

// 自动导入视图
async function autoImport() {
  let views = await getViewsNames();

  for (let item of views) {
    let templateContent = await getTemplateContent(item);
    renderElement(`cjs-${item}`, templateContent);
  }
}

autoImport();

export { autoImport };
